package com.moyun.controller.quartz;

import com.moyun.common.annotation.OperLog;
import com.moyun.common.aspect.BusinessType;
import com.moyun.model.common.R;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.quartz.*;
import org.quartz.impl.JobDetailImpl;
import org.quartz.impl.matchers.GroupMatcher;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.quartz.SchedulerFactoryBean;
import org.springframework.web.bind.annotation.*;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;

/**
 * <h3>moyun-base</h3>
 * <p>定时任务的控制层</p>
 *
 * @author : ybx
 * @date : 2021-08-19 14:47:57
 **/
@Api(tags = "系统定时任务")
@Slf4j
@RestController
@RequestMapping("/time-task")
public class QuartzController {
    @Autowired
    private SchedulerFactoryBean springScheduler;

    @Autowired
    private Scheduler scheduler;

    // 查看所有定时任务
    @ApiOperation("定时任务查询")
    @GetMapping(value = "/select")
    public R selectAllTimeTask() {

        ArrayList<Trigger> triggers = new ArrayList<>();
        try {
//            //获取Scheduler
//            Scheduler scheduler = springScheduler.getScheduler();
            //再获取Scheduler下的所有group
            List<String> triggerGroupNames = scheduler.getTriggerGroupNames();
            for (String groupName : triggerGroupNames) {
                //组装group的匹配，为了模糊获取所有的triggerKey或者jobKey
                GroupMatcher groupMatcher = GroupMatcher.groupEquals(groupName);
                //获取所有的triggerKey
                Set<TriggerKey> triggerKeySet = scheduler.getTriggerKeys(groupMatcher);
                for (TriggerKey triggerKey : triggerKeySet) {
                    //通过triggerKey在scheduler中获取trigger对象
//                        CronTrigger cronTrigger = (CronTrigger) scheduler.getTrigger(triggerKey);
                    SimpleTrigger simpleTrigger = (SimpleTrigger) scheduler.getTrigger(triggerKey);
                    Trigger trigger = scheduler.getTrigger(triggerKey);
                    Trigger.TriggerState triggerState = scheduler.getTriggerState(triggerKey);

                    MyTrigger myTrigger = new MyTrigger();
                    //获取trigger拥有的Job
                    JobKey jobKey = trigger.getJobKey();
                    JobDetailImpl jobDetail = (JobDetailImpl) scheduler.getJobDetail(jobKey);
                    //组装页面需要显示的数据
//                        QuartzJobsVO quartzJobsVO = new QuartzJobsVO();
//                        quartzJobsVO.setGroupName(groupName);
//                        quartzJobsVO.setJobDetailName(jobDetail.getName());
//                        quartzJobsVO.setJobCronExpression(trigger.getCronExpression());
//                        quartzJobsVO.setTimeZone(trigger.getTimeZone().getID());
//                        quartzJobsVOList.add(quartzJobsVO);
                    myTrigger.setTrigger(trigger);
                    boolean b = "NORMAL".equals(triggerState.name());
                    JobKey jobKey1 = trigger.getJobKey();
                    myTrigger.setTriggerState(b);
                    triggers.add(myTrigger);
                }
            }
        } catch (Exception e) {
            log.warn("获取定时任务信息出错");
        }
        return R.ok(triggers);
    }

    /**
     * @return void
     * @Author yangboxuan
     * @Description 刷新定时任务(这里是simpleSchduler形式)
     * @Date 2021/6/16 18:27
     * @Param []
     **/
    @ApiOperation("刷新定时任务")
    @GetMapping(value = "/reresh-shedule-trigger")
    public R retScheduleJob(@RequestParam("triggerName") String triggerName, @RequestParam("intervalTime") Integer intervalTime) throws SchedulerException {
        try {
            TriggerKey triggerKey = TriggerKey.triggerKey(triggerName, "DEFAULT");
//            TriggerKey triggerKey = TriggerKey.triggerKey("BpmMainDataMonitor", "DEFAULT");
            SimpleTrigger trigger = (SimpleTrigger) scheduler.getTrigger(triggerKey);
            if (trigger == null) {
                return R.error("未查找到对应的定时任务");
            }
            // 新建一个触发器
            TriggerBuilder<Trigger> triggerBuilder = TriggerBuilder.newTrigger();
            // 触发器名,触发器组
            triggerBuilder.withIdentity(triggerName, "DEFAULT");
            triggerBuilder.startNow();
            // 触发器时间设定
            triggerBuilder.withSchedule(SimpleScheduleBuilder.simpleSchedule().withIntervalInSeconds(intervalTime).repeatForever());
            // 创建Trigger对象
            Trigger trigger1 = triggerBuilder.build();
            // 方式一 ：修改一个任务的触发时间
            scheduler.rescheduleJob(triggerKey, trigger1);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
        return R.ok("操作成功");
    }

    /**
     * @return java.lang.Object
     * @Author yangboxuan
     * @Description 定时任务停止
     * @Date 2021/6/16 18:46
     * @Param [orderNo]
     **/
    @ApiOperation("暂停定时任务")
    @GetMapping("/pause")
    public R shutdown(@RequestParam("triggerName") String triggerName) throws IOException, SchedulerException {
        // TODO: 2022/9/7 添加triggerName的校验
        scheduler.pauseTrigger(TriggerKey.triggerKey(triggerName, "DEFAULT"));//暂停Trigger
        return R.ok("操作成功");
    }

    /**
     * @return java.lang.Object
     * @Author yangboxuan
     * @Description 定时任务恢复
     * @Date 2021/6/16 18:46
     * @Param [orderNo]
     **/
    @ApiOperation("恢复定时任务")
    @GetMapping("/resume")
    public R resume(@RequestParam("triggerName") String triggerName) throws IOException, SchedulerException {
        scheduler.resumeTrigger(TriggerKey.triggerKey(triggerName));//恢复Trigger
        return R.ok("操作成功");
    }

    /**
     * @return com.moyun.common.web.JsonResult
     * @Author yangboxuan
     * @Description 删除系统中的定时任务
     * @Date 2021/8/19 17:03
     * @Param [group, name]
     **/
    @ApiOperation("删除定时任务")
    @OperLog(operModul = "定时任务", operType = BusinessType.DELETE, operDesc = "删除指定的定时任务")
    @DeleteMapping("/delete")
    public R delete(@RequestParam("group") String group, @RequestParam("name") String name) throws SchedulerException {

        if (scheduler.deleteJob(new JobKey(name, group))) {
            return R.ok("删除成功");
        } else {
            return R.error("删除失败");
        }
    }


}
